package com.yida.gwj.expend.outside.service.impl;

import java.math.BigDecimal;
import java.util.ArrayList;
import java.util.HashMap;
import java.util.LinkedHashMap;
import java.util.List;
import java.util.Map;

import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import com.yida.common.core.constant.SecurityConstants;
import com.yida.common.core.domain.R;
import com.yida.common.core.exception.ServiceException;
import com.yida.common.core.utils.PageUtils;
import com.yida.common.core.utils.StringUtils;
import com.yida.gwj.api.domain.dto.GwjExpendHouseAndOwnerDTO;
import com.yida.gwj.api.domain.dto.GwjGVoteResultInnerDTO;
import com.yida.gwj.api.domain.request.GwjVoteResultInnerRequest;
import com.yida.gwj.api.service.RemoteGwjVoteService;
import com.yida.gwj.expend.outside.domain.GwjMaintenanceFundsBusiness;
import com.yida.gwj.expend.outside.domain.GwjMaintenanceFundsBusinessHouse;
import com.yida.gwj.expend.outside.domain.GwjMaintenanceFundsBusinessInfo;
import com.yida.gwj.expend.outside.domain.GwjMaintenanceFundsBusinessOwner;
import com.yida.gwj.expend.outside.domain.request.GwjHouseAndOwnerRequest;
import com.yida.gwj.expend.outside.domain.request.GwjMaintenanceFundsBusinessRequest;
import com.yida.gwj.expend.outside.mapper.GwjExpendHouseAndOwnerMapper;
import com.yida.gwj.expend.outside.mapper.GwjMaintenanceFundsBusinessMapper;
import com.yida.gwj.expend.outside.service.GwjExpendOutsideBaseHouseService;
import com.yida.gwj.expend.outside.service.IGwjMaintenanceFundsBusinessHouseService;
import com.yida.gwj.expend.outside.service.IGwjMaintenanceFundsBusinessInfoService;
import com.yida.gwj.expend.outside.service.IGwjMaintenanceFundsBusinessOwnerService;

import cn.hutool.core.util.ObjectUtil;

/**
 * @author hmh
 * @date 2023/06/17
 */
@Service
public class GwjExpendOutsideBaseHouseServiceImpl implements GwjExpendOutsideBaseHouseService {

    private static final Logger log = LoggerFactory.getLogger(GwjExpendOutsideBaseHouseServiceImpl.class);

    @Autowired
    private IGwjMaintenanceFundsBusinessHouseService iGwjMaintenanceFundsBusinessHouseService;

    @Autowired
    private IGwjMaintenanceFundsBusinessOwnerService iGwjMaintenanceFundsBusinessOwnerService;

    @Autowired
    private GwjExpendHouseAndOwnerMapper gwjExpendHouseAndOwnerMapper;

    @Autowired
    private RemoteGwjVoteService remoteGwjVoteService;

    @Autowired
    private IGwjMaintenanceFundsBusinessInfoService gwjMaintenanceFundsBusinessInfoService;

    @Autowired
    private GwjMaintenanceFundsBusinessMapper gwjMaintenanceFundsBusinessMapper;

    /* 
     * 根据业务ID更改房屋和业主信息
     */
    @Override
    public boolean updatBusinessHouseAndOwnerInfoByBizId(GwjHouseAndOwnerRequest gwjHouseAndOwnerRequest) {
        if (gwjHouseAndOwnerRequest.getBizId() > 0 && StringUtils.isNotNull(gwjHouseAndOwnerRequest.getHouseCode())) {
            // 除非数据操作异常否则当成功！
            // 原始房屋数据
            // 获取房屋数据
            GwjMaintenanceFundsBusinessHouse gmfbh = iGwjMaintenanceFundsBusinessHouseService.selectGwjMaintenanceFundsBusinessHouseByBizIdAndHouseCode(gwjHouseAndOwnerRequest.getBizId(), gwjHouseAndOwnerRequest.getHouseCode());
            // 已选中，非公用户进行修改
            if (gmfbh.getSelectFlag() != 1 && gmfbh.getPublicFlag() != 0) {
                throw new ServiceException("不允许修改未选中或者公用户房屋信息！");
            }
            // 因为前端调用该方法是使用单个字段上传，这里增加判断，减少操作
            upHouseInfo(gmfbh, gwjHouseAndOwnerRequest);
            upOwnerInfo(gwjHouseAndOwnerRequest);
            return true;
        }
        return false;
    }

    /**
     * 业务逻辑参照com.yida.gwj.expend.outside.service.impl.GwjMaintenanceFundsBusinessServiceImpl下的shareEquallyMoneyUpdate方法
     * 后期问题再进行调整
     * 
     * 实际分摊金额=差额+应分摊金额
     * 
     * 本次分摊总金额=差额+应分摊金额+自筹金额
     * 
     * @param gwjHouseAndOwnerRequest
     */
    @Transactional(rollbackFor = Exception.class)
    private void upHouseInfo(GwjMaintenanceFundsBusinessHouse gmfbh, GwjHouseAndOwnerRequest gwjHouseAndOwnerRequest) {
        if (gwjHouseAndOwnerRequest.getLackMoney() == null && gwjHouseAndOwnerRequest.getSelfRaiseMoney() == null) {
            return;
        }
        // 获取当前房屋数据

        // 获取当前房屋未修改前数据
        // 历史差额
        BigDecimal oldLackMoney = gmfbh.getLackMoney();
        // 历史实际分摊金额
        BigDecimal allocationMoney = gmfbh.getAllocationMoney();
        // 历史实际分摊金额
        BigDecimal oldActualAllocationMoney = gmfbh.getActualAllocationMoney();
        // 历史自筹金额
        BigDecimal oldSelfRaiseMoney = gmfbh.getSelfRaiseMoney();
        // 本次分摊总金额
        // BigDecimal oldTotalAllocationMoney = gmfbh.getTotalAllocationMoney();
        // 变动房屋数据
        // 差额
        BigDecimal requestLackMoney = gwjHouseAndOwnerRequest.getLackMoney();
        // BigDecimal changeLackMoney = StringUtils.isNull(requestLackMoney) ? new BigDecimal(0) : requestLackMoney;
        BigDecimal changeLackMoney = StringUtils.isNull(requestLackMoney) ? oldLackMoney : requestLackMoney;
        // 自筹金额
        BigDecimal requestSelfRaiseMoney = gwjHouseAndOwnerRequest.getSelfRaiseMoney();
        // BigDecimal changeSelfRaiseMoney = StringUtils.isNull(requestSelfRaiseMoney) ? new BigDecimal(0) :
        // requestSelfRaiseMoney;
        BigDecimal changeSelfRaiseMoney = StringUtils.isNull(requestSelfRaiseMoney) ? oldSelfRaiseMoney : requestSelfRaiseMoney;
        // 当前变动的实际分摊金额(历史实际分摊金额-历史差额+变动差额)
        BigDecimal changeActualAllocationMoney = allocationMoney.add(changeLackMoney);
        // 当前变动本次分摊总金额(变更后的实际分摊金额+变更自筹金额)
        BigDecimal changeTotalAllocationMoney = allocationMoney.add(changeLackMoney).add(changeSelfRaiseMoney);
        // 注：精度缺失情况下，考虑保留两位小数
        // 更新当前房屋数据
        iGwjMaintenanceFundsBusinessHouseService.updateGwjMaintenanceFundsBusinessHouse(new GwjMaintenanceFundsBusinessHouse() {
            /**
             *
             */
            private static final long serialVersionUID = 4019494863942169353L;
            {
                // 业务ID
                setBizId(gwjHouseAndOwnerRequest.getBizId());
                // 房屋标识码
                setHouseCode(gwjHouseAndOwnerRequest.getHouseCode());
                // 差额
                setLackMoney(requestLackMoney);// 改换请求参数，避免转换为0时重置了结果
                // 自筹金额
                setSelfRaiseMoney(requestSelfRaiseMoney);
                // 实际分摊金额
                setActualAllocationMoney(changeActualAllocationMoney);
                // 本次分摊总金额
                setTotalAllocationMoney(changeTotalAllocationMoney);
            }
        });
        // 更新当前业务数据
        // 获取当前业务金额统计数据
        Map<String, Object> countMoneyMap = gwjExpendHouseAndOwnerMapper.countHoustMoney(gwjHouseAndOwnerRequest.getBizId());
        // 获取总差额
        // countMoneyMap.get("total_lack_money");
        // 获取总实际分摊金额
        BigDecimal total_actual_allocation_money = new BigDecimal(countMoneyMap.get("total_actual_allocation_money").toString());
        // total_actual_allocation_money = total_actual_allocation_money.subtract(oldLackMoney).add(changeLackMoney);
        // 获取总自筹金额
        // countMoneyMap.get("total_self_raise_money");
        // 获取总分摊总金额
        BigDecimal total_total_allocation_money = new BigDecimal(countMoneyMap.get("total_total_allocation_money").toString());
        // 总得实际分摊金额+变动自筹金额
        // BigDecimal total_total_allocation_money = total_actual_allocation_money.add(changeSelfRaiseMoney);
        gwjMaintenanceFundsBusinessInfoService.updateGwjMaintenanceFundsBusinessInfo(new GwjMaintenanceFundsBusinessInfo() {
            {
                setBizId(gwjHouseAndOwnerRequest.getBizId());
                setActualAllocationAmount(total_actual_allocation_money);
                setTotalAllocatedSettlementAmount(total_total_allocation_money);
            }
        });
    }

    @Transactional(rollbackFor = Exception.class)
    private void upOwnerInfo(GwjHouseAndOwnerRequest gwjHouseAndOwnerRequest) {
        // 三个值都为空不进行调用操作
        if (StringUtils.isNull(gwjHouseAndOwnerRequest.getOwnerName()) && StringUtils.isNull(gwjHouseAndOwnerRequest.getPhone()) && StringUtils.isNull(gwjHouseAndOwnerRequest.getCardNum())) {
            return;
        }
        // 待操作数据
        GwjMaintenanceFundsBusinessOwner opGwjMaintenanceFundsBusinessOwner = new GwjMaintenanceFundsBusinessOwner() {
            /**
            *
            */
            private static final long serialVersionUID = -2988855505227945676L;

            {
                // 业务ID
                setBizId(gwjHouseAndOwnerRequest.getBizId());
                // 房屋标识码
                setHouseCode(gwjHouseAndOwnerRequest.getHouseCode());
                // 名称
                setOwnerName(gwjHouseAndOwnerRequest.getOwnerName());
                // 手机号
                setPhone(gwjHouseAndOwnerRequest.getPhone());
                // 身份证号
                setCardNum(gwjHouseAndOwnerRequest.getCardNum());
            }
        };
        GwjMaintenanceFundsBusinessOwner rGwjMaintenanceFundsBusinessOwner = iGwjMaintenanceFundsBusinessOwnerService.selectGwjMaintenanceFundsBusinessOwnerByBizIdAndHouseCode(gwjHouseAndOwnerRequest.getBizId(), gwjHouseAndOwnerRequest.getHouseCode());
        if (StringUtils.isNull(rGwjMaintenanceFundsBusinessOwner)) {
            // 空进行新增
            iGwjMaintenanceFundsBusinessOwnerService.insertGwjMaintenanceFundsBusinessOwner(opGwjMaintenanceFundsBusinessOwner);
            return;
        }
        // 否则进行修改
        iGwjMaintenanceFundsBusinessOwnerService.updateGwjMaintenanceFundsBusinessOwnerByBizIdAndHouseCode(opGwjMaintenanceFundsBusinessOwner);
    }

    /* 
     * 检查业主信息
     */
    @Override
    public boolean checkOwnerInfo(Long bizId) {
        // 目前只显示10条未正确输入业主信息记录
        List<LinkedHashMap<String, Object>> list = gwjExpendHouseAndOwnerMapper.checkOwnerInfo(bizId);
        if (StringUtils.isNotEmpty(list)) {
            StringBuffer sb = new StringBuffer();
            list.stream().forEach(m -> {
                sb.append("房屋编号").append(m.get("houseCode")).append("：");
                String ownerNameMsg = StringUtils.isEmpty((String)m.get("ownerName")) ? "业主姓名为空！；" : "";
                sb.append(ownerNameMsg);
                String cardNumMsg = StringUtils.isEmpty((String)m.get("cardNum")) ? "业主身份证为空！；" : "";
                sb.append(cardNumMsg);
                String phoneMsg = StringUtils.isEmpty((String)m.get("phone")) ? "业主手机号为空！；" : "";
                sb.append(phoneMsg).append("\n");
            });
            throw new ServiceException("当前业务存在未处理业务信息: \n" + sb.toString());
        }
        return true;

    }

    /* 
     * 
     */
    @Override
    public List<String> selectHouseUseType(Long bizId) {
        List<String> list = gwjExpendHouseAndOwnerMapper.selectHouseUseType(bizId);
        list.add(0, "全部");
        return list;
    }

    /* 
     * 查询房屋业主投票列表
     */
    @Override
    public List<GwjExpendHouseAndOwnerDTO> selectHouseAndOwnerVoteInfosByBizIdAndBizNum(Long bizId, Long bizNum) {
        // PageUtils.startPage();
        List<GwjExpendHouseAndOwnerDTO> list = gwjExpendHouseAndOwnerMapper.selectGwjExpendHouseAndOwnerList(bizId);
        if (StringUtils.isEmpty(list)) {
            return new ArrayList<GwjExpendHouseAndOwnerDTO>();
        }
        List<String> cardNumArray = new ArrayList<String>();
        list.stream().forEach(gehao -> {
            String cardNum = gehao.getCardNum();
            if (StringUtils.isNotEmpty(cardNum)) {
                cardNumArray.add(cardNum);
            }
        });
        // 获取公维金投票结果
        Map<String, String> gVoteResultMap = getVoteInfosByBizNum(bizNum, cardNumArray);
        String voteDefault = "未选择";
        list.stream().forEach(gehao -> {
            String cardNum = gehao.getCardNum();
            System.out.println("cardNum:" + cardNum);
            // 优先判断身份证内是否有投票信息
            String cardNumVoteResult = gVoteResultMap.get(cardNum);
            // 身份证不为空，获取对应投票结果，如果投票结果为空则赋默认值;身份证号为空则赋默认值
            String voteResult = StringUtils.isNotEmpty(cardNum) ? (StringUtils.isNotEmpty(cardNumVoteResult) ? cardNumVoteResult : voteDefault) : voteDefault;
            if (StringUtils.isNotEmpty(voteResult) && !voteDefault.equals(voteResult)) {
                gehao.setOwnerOpinion(voteResult);
                return;
            }
            // 再度判断手机号内是否有投票信息
            String phonenumber = gehao.getPhonemumber();
            System.out.println("phonenumber:" + phonenumber);
            // 手机号不为空，获取对应投票结果，如果投票结果为空则赋默认值;手机号空则赋默认值
            String phonenumberVoteResult = gVoteResultMap.get(phonenumber);
            voteResult = StringUtils.isNotEmpty(phonenumber) ? (StringUtils.isNotEmpty(phonenumberVoteResult) ? phonenumberVoteResult : voteDefault) : voteDefault;
            gehao.setOwnerOpinion(voteResult);
        });
        return list;
    }

    /**
     * 查询房屋业主投票列表
     * 
     * @param outServerIdentification 业务标识
     * @return
     */
    @Override
    public List<GwjExpendHouseAndOwnerDTO> selectHouseAndOwnerVoteInfos(String outServerIdentification) {
        GwjMaintenanceFundsBusiness gwjMaintenanceFundsBusiness = gwjMaintenanceFundsBusinessMapper.getGwjMaintenanceFundsBusiness(new GwjMaintenanceFundsBusinessRequest() {
            {
                setServerIdentification(outServerIdentification);
            }
        });
        if (ObjectUtil.isEmpty(gwjMaintenanceFundsBusiness)) {
            gwjMaintenanceFundsBusiness = gwjMaintenanceFundsBusinessMapper.getGwjMaintenanceFundsBusiness(new GwjMaintenanceFundsBusinessRequest() {
                {
                    setOutServerIdentification(outServerIdentification);
                }
            });
            if (ObjectUtil.isEmpty(gwjMaintenanceFundsBusiness)) {
                throw new ServiceException("未查询到对应业务信息");
            }
        }
        PageUtils.startPage();
        return this.selectHouseAndOwnerVoteInfosByBizIdAndBizNum(gwjMaintenanceFundsBusiness.getBizId(), gwjMaintenanceFundsBusiness.getBizNum());
    }

    private Map<String, String> getVoteInfosByBizNum(Long bizNum, List<String> cardNumArray) {
        Map<String, String> resultMap = new HashMap<String, String>();
        // 获取投票结果
        GwjVoteResultInnerRequest request = new GwjVoteResultInnerRequest();
        request.setBizNum(bizNum);
        request.setOwnerCards(cardNumArray);
        R<List<GwjGVoteResultInnerDTO>> result = remoteGwjVoteService.innerVoteResult(request, SecurityConstants.INNER);
        if (R.FAIL == result.getCode()) {
            log.error(result.getMsg());
            // throw new ServiceException("未获取到业务编号" + bizNum + "的投票结果！请核对投票信息！");
            return resultMap;
        }
        List<GwjGVoteResultInnerDTO> list = result.getData();
        list.stream().forEach(gvri -> {
            String option = gvri.getOptionName();
            resultMap.put(gvri.getOwnerPhone(), option);
            resultMap.put(gvri.getOwnerCard(), option);
        });
        return resultMap;
    }

    public static void main(String[] args) {
        // Object o = null;
        // // String s = null;
        // // new String((String)o);
        // String cardNumMsg = StringUtils.isEmpty((String)o) ? "业主身份证为空！；" : "";
        // System.out.println("cardNumMsg：" + cardNumMsg);

        // Map<String, String> resultMap = new HashMap<String, String>();
        //
        // System.out.println(resultMap.get("test"));
        // BigDecimal changeLackMoney = gwjHouseAndOwnerRequest.getLackMoney();

        // BigDecimal changeLackMoney = new BigDecimal(1.1);
        //
        // // BigDecimal changeLackMoney = null;
        // changeLackMoney = StringUtils.isNull(changeLackMoney) ? new BigDecimal(0) : changeLackMoney;
        // System.out.println(changeLackMoney);
        // BigDecimal changeLackMoney1 = new BigDecimal(1.11);
        // BigDecimal s = NumberUtil.sub(changeLackMoney, changeLackMoney1);
        // System.out.println("s:" + s);
        // BigDecimal a = NumberUtil.add(changeLackMoney, changeLackMoney1);
        // System.out.println("a:" + a);

        // GwjMaintenanceFundsBusinessHouse maintenanceFundsBusinessHouse = new GwjMaintenanceFundsBusinessHouse();
        // maintenanceFundsBusinessHouse.setLackMoney(new BigDecimal("1.1"));
        // BigDecimal s = maintenanceFundsBusinessHouse.getLackMoney();
        // s = s.add(s);
        // System.out.println(s);

        // total_actual_allocation_money
        BigDecimal i = new BigDecimal("1.21");
        BigDecimal j = new BigDecimal("2.21");
        i = i.add(j);
        BigDecimal x = null;
        System.out.println(x.compareTo(BigDecimal.ZERO) == 0);
        System.out.println(i);
    }

}
